// ====================CardGauge====================

class CardHpGauge extends CardContainerBase {
    initialize() {
        this._battler = null;
        this._hp = NaN;
        this._maxHp = NaN;
        this._targetHp = NaN;
        this._targetMaxHp = NaN;
        this._duration = 0;
        this._armor = 0;
        this.create();
    }

    setObject(battler) {
        this._battler = battler;
        this.drawName();
    }

    create() {
        this.createBackgroundLayer();
        this.createNameLayer();
        this.createArmorLayer();
        this.createArmorIcon();
        this.createArmorTextLayer();
        this.createValueLayer();
        this.createTextLayer();

    }

    createBackgroundLayer() {
        const {width, height, rim, bgColour} = this._opts;
        const bitmap = new Bitmap(width, height);
        const sprite = new Sprite(bitmap);
        const r = Math.floor(height / 2);
        bitmap.fillRoundRect(0, 0, width, height, bgColour, r);
        this._backgroundLayer = sprite;
        this.addChild(sprite);
    }

    createNameLayer() {
        const {width, height} = this._opts;
        const bitmap = new Bitmap(width, height);
        const sprite = new Sprite(bitmap);
        bitmap.fontSize = height - 4;
        this._nameLayer = sprite;
        this.addChild(sprite);
        sprite.move(0, -height - 5);
    }

    createArmorLayer() {
        const {width, height} = this._opts;
        const rim = 3
        const bitmap = new Bitmap(width + rim * 2, height + rim * 2);
        const sprite = new Sprite(bitmap);
        const x = -rim;
        const y = -rim;
        const r = Math.floor(height / 2) + rim;
        bitmap.fillRoundRect(0, 0, width + rim * 2, height + rim * 2, "#FFFFFF", r);
        this._armorLayer = sprite;
        this.addChild(sprite);
        sprite.move(x, y);
        sprite.hide();
    }

    createArmorIcon() {
        const {height} = this._opts;
        const bitmap = new Bitmap(32, 32);
        const sprite = new Sprite(bitmap);
        const x = -35;
        const y = -Math.floor((32 - height) / 2);
        const iconIndex = 128;
        bitmap.drawIcon(iconIndex, 0, 0, 32, 32);
        this._armorIcon = sprite;
        this.addChild(sprite);
        sprite.move(x,y);
        sprite.hide();
    }

    createArmorTextLayer() {
        const {height} = this._opts;
        const bitmap = new Bitmap(32, 32);
        const sprite = new Sprite(bitmap);
        const x = -35;
        const y = -Math.floor((32 - height) / 2);
        bitmap.fontSize = 25;
        bitmap.fontFace = $gameSystem.mainFontFace();
        this._armorTextLayer = sprite;
        this.addChild(sprite);
        sprite.move(x,y);
        sprite.hide();
    }



    createValueLayer() {
        const {width, height, rim, vColour} = this._opts;
        const bitmap = new Bitmap(width, height);
        const sprite = new Sprite(bitmap);
        const r = Math.floor(height / 2);
        bitmap.fontSize = height - 4;
        bitmap.fillRoundRect(0, 0, width, height, vColour, r);
        this._valueLayer = sprite;
        this.addChild(sprite);
    }

    createTextLayer() {
        const {width, height, rim} = this._opts;
        const r = height / 2 - rim;
        const bitmap = new Bitmap(width, height);
        const sprite = new Sprite(bitmap);
        bitmap.fontSize = 15;
        bitmap.fontFace = $gameSystem.mainFontFace();
        this._textLayer = sprite;
        this.addChild(sprite);
    }

    drawName() {
        const bitmap = this._nameLayer.bitmap;
        const name = this._battler.name();
        bitmap.clear();
        bitmap.drawText(name, 3, 0, bitmap.width, bitmap.height);
    }

    update() {
        for (const layer of this.children) {
            layer.update();
        }
        if (this.needRefreshHp()) {
            this.updateGauge();
        }
        if (this.needRefreshArmor()) {
            this.updateArmor();
        }
        this.updateGaugeAnimation();
    }

    updateGauge() {
        const batter = this._battler;
        const value = batter.hp;
        const maxValue = batter.mhp;
        this._targetValue = value;
        this._targetMaxValue = maxValue;
        if (isNaN(this._value)) {
            this._value = value;
            this._maxValue = maxValue;
            this.redraw();
        } else {
            this._duration = 20;
        }
    }

    updateGaugeAnimation() {
        if (this._duration > 0) {
            const d = this._duration;
            this._value = (this._value * (d - 1) + this._targetValue) / d;
            this._maxValue = (this._maxValue * (d - 1) + this._targetMaxValue) / d;
            this._duration--;
            this.redraw();
        }
    }

    updateArmor() {
        const bitmap = this._armorTextLayer.bitmap;
        this._armor = this._battler.am;
        bitmap.clear();
        if (this._armor === 0) {
            this._armorIcon.hide();
            this._armorLayer.hide();
            this._armorTextLayer.hide();
            return;
        }
        this._armorIcon.show();
        this._armorLayer.show();
        this._armorTextLayer.show();
        bitmap.drawText(this._armor, 0, 0, 32, 32,"center");
    }

    redraw() {
        const {width, height, rim} = this._opts;
        const value = this._value;
        const maxValue = this._maxValue;
        const rate = maxValue > 0 ? value / maxValue : 0;
        const valueText = `${Math.floor(value)}/${Math.floor(maxValue)}`;
        const w = Math.floor(width * rate);
        this._valueLayer.setFrame(0, 0, w, height);
        this._textLayer.bitmap.clear();
        this._textLayer.bitmap.drawText(valueText, 0, 0, width, height, "center");
    }

    needRefreshHp() {
        const battler = this._battler;
        return !!battler && (battler.hp !== this._targetValue || battler.mhp !== this._targetMaxValue);
    }

    needRefreshArmor() {
        return !!this._battler && this._armor !== this._battler.am;
    }

    destroy() {
        this._backgroundLayer.bitmap.destroy();
        this._nameLayer.bitmap.destroy();
        this._armorLayer.bitmap.destroy();
        this._armorIcon.bitmap.destroy();
        this._armorTextLayer.bitmap.destroy();
        this._valueLayer.bitmap.destroy();
        this._textLayer.bitmap.destroy();
        super.destroy();
    }
}